package com.cykj.pos.controller.api;

import com.alibaba.fastjson.JSONObject;
import com.cykj.common.annotation.Log;
import com.cykj.common.core.controller.BaseController;
import com.cykj.common.core.domain.AjaxResult;
import com.cykj.common.core.domain.entity.SysUser;
import com.cykj.common.core.page.TableDataInfo;
import com.cykj.common.enums.BusinessType;
import com.cykj.common.utils.SecurityUtils;
import com.cykj.common.utils.poi.ExcelUtil;
import com.cykj.pos.domain.*;
import com.cykj.pos.domain.dto.CashOutDTO;
import com.cykj.pos.mapper.BizPosMachineMapper;
import com.cykj.pos.service.*;
import com.cykj.pos.util.HexUtils;
import com.cykj.pos.util.LoginUserUtils;
import com.google.gson.Gson;
import io.swagger.annotations.ApiOperation;
import lombok.RequiredArgsConstructor;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.util.EntityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.*;

import javax.servlet.http.HttpServletRequest;
import java.io.IOException;
import java.nio.charset.Charset;
import java.security.MessageDigest;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.*;


/**
 * 商户下发收款者Controller
 *
 * @author xxl
 * @date 2022-03-24
 */
@RequiredArgsConstructor(onConstructor_ = @Autowired)
@RestController
@RequestMapping("/pos/receiver")
public class PosV2AppMerchantReceiverController extends BaseController {

    private final IBizMerchantReceiverService iBizMerchantReceiverService;

    private final IBizMicroInfoService bizMicroInfoService;

    private final IBizMessageRecordsService bizMessageRecordsService;

    private final IBizWalletService walletService;

    private final IBizMerchantService bizMerchantService;

    private final BizPosMachineMapper posMachineMapper;;
    //API对接配置 --商户签名密钥
    String signGenerationKey = "b0f2225345674c36aaa8da44e1c05e56";
    //API对接配置 --默认签名方式
    String signType = "SHA256";
    //API对接配置 --商户ID
    String merchantId = "k34zj89kCA958qJMF1fC";
    //API对接配置 --渠道ID
    String partnerId = "JRMF";
    //下发公司id
    String id = "10247019";

    /**
     * 查询商户下发收款者列表
     */
    @PreAuthorize("@ss.hasPermi('pos:receiver:list')")
    @GetMapping("/list")
    public TableDataInfo list(BizMerchantReceiver bizMerchantReceiver) {
        startPage();
        List<BizMerchantReceiver> list = iBizMerchantReceiverService.queryList(bizMerchantReceiver);
        return getDataTable(list);
    }

    /**
     * 导出商户下发收款者列表
     */
    @PreAuthorize("@ss.hasPermi('pos:receiver:export')")
    @Log(title = "商户下发收款者", businessType = BusinessType.EXPORT)
    @GetMapping("/export")
    public AjaxResult export(BizMerchantReceiver bizMerchantReceiver) {
        List<BizMerchantReceiver> list = iBizMerchantReceiverService.queryList(bizMerchantReceiver);
        ExcelUtil<BizMerchantReceiver> util = new ExcelUtil<BizMerchantReceiver>(BizMerchantReceiver.class);
        return util.exportExcel(list, "receiver");
    }

    /**
     * 获取商户下发收款者详细信息
     */
    @PreAuthorize("@ss.hasPermi('pos:receiver:query')")
    @GetMapping(value = "/{id}")
    public AjaxResult getInfo(@PathVariable("id") Long id) {
        return AjaxResult.success(iBizMerchantReceiverService.getById(id));
    }

    /**
     * 新增商户下发收款者
     */
    @PreAuthorize("@ss.hasPermi('pos:receiver:add')")
    @Log(title = "商户下发收款者", businessType = BusinessType.INSERT)
    @PostMapping
    public AjaxResult add(@RequestBody BizMerchantReceiver bizMerchantReceiver) {
        return toAjax(iBizMerchantReceiverService.save(bizMerchantReceiver) ? 1 : 0);
    }

    /**
     * 修改商户下发收款者
     */
    @PreAuthorize("@ss.hasPermi('pos:receiver:edit')")
    @Log(title = "商户下发收款者", businessType = BusinessType.UPDATE)
    @PutMapping
    public AjaxResult edit(@RequestBody BizMerchantReceiver bizMerchantReceiver) {
        return toAjax(iBizMerchantReceiverService.updateById(bizMerchantReceiver) ? 1 : 0);
    }

    /**
     * 删除商户下发收款者
     */
    @PreAuthorize("@ss.hasPermi('pos:receiver:remove')")
    @Log(title = "商户下发收款者", businessType = BusinessType.DELETE)
    @DeleteMapping("/{ids}")
    public AjaxResult remove(@PathVariable Long[] ids) {
        return toAjax(iBizMerchantReceiverService.removeByIds(Arrays.asList(ids)) ? 1 : 0);
    }

    @PostMapping("/echoReceiver")
    @Transactional
    public AjaxResult echoReceiver(@RequestBody BizMerchant bizMerchant){
        AjaxResult ajaxResult = AjaxResult.success("查询商户是否签约");
//        SysUser user= SecurityUtils.getLoginUser().getUser();
//        if(posMachineMapper.getDeptid(user.getUserId())!=117){
//            ajaxResult.put("data","2");
//            ajaxResult.put("ret_msg","商户已签约");
//            return ajaxResult;
//        }

      BizMerchantReceiver bizMerchantReceiver =  bizMerchantService.selectBizMerchantReceiver(bizMerchant);
      if (bizMerchantReceiver == null){
          ajaxResult.put("data","0");
          ajaxResult.put("ret_msg","商户未签约");
          return ajaxResult;
      }
      if (bizMerchantReceiver.getContractStatus().equals("0")){
          ajaxResult.put("data","0");
          ajaxResult.put("ret_msg","商户未签约");
          return ajaxResult;
      }else if(bizMerchantReceiver.getContractStatus().equals("2")){
          ajaxResult.put("data","2");
          ajaxResult.put("ret_msg","商户签约审核中");
          return ajaxResult;
      }else if (bizMerchantReceiver.getContractStatus().equals("1")){
          ajaxResult.put("data","1");
          ajaxResult.put("ret_msg",bizMerchantReceiver.getErroMessage());
          return ajaxResult;
      }else {
          ajaxResult.put("data","3");
          ajaxResult.put("ret_msg","商户已签约");
          return ajaxResult;
      }
    }
    @ApiOperation("新增加商户下发收款者")
    @PostMapping("/addReceiverNew")
    @Transactional
    public AjaxResult addReceiverNew(@RequestBody BizMerchantReceiver bizMerchantReceiver) throws IOException {
        System.out.println("--------------------------");
        System.out.println("--------------------------");
        System.out.println("---------增加商户下发收款者-----------------");
        System.out.println("--------------------------");
        AjaxResult ajaxResult = AjaxResult.success("增加商户下发收款者");
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        Date date = new Date();
        String merchId = bizMerchantService.selectMerchId(bizMerchantReceiver.getUserId().toString());
        bizMerchantReceiver.setMerchId(Long.parseLong(merchId));
        //先查询商户下发收款者是否存在
        // BizMerchantReceiver bizMerchantReceiver1 = iBizMerchantReceiverService.selectBizMerchantReceiverByUserId(bizMerchantReceiver.getUserId());
        BizMerchantReceiver bizMerchantReceiver1 = iBizMerchantReceiverService.selectBizMerchantReceiverByMerchId(bizMerchantReceiver);
        if (bizMerchantReceiver1 != null ){
            iBizMerchantReceiverService.removeById(bizMerchantReceiver1.getId());
        }
        /**/
        BizMicroInfo bizMicroInfoByMerchId = bizMicroInfoService.getBizMicroInfoByMerchId(Long.parseLong(merchId));
        String url = "https://b.hndbdj.com/api/contract/addmerchanttransferreceiver.do";
        SimpleDateFormat df = new SimpleDateFormat("yyyyMMddHHmmssSSS");
        String timestamp = df.format(System.currentTimeMillis());
        Map<String, String> data = new HashMap<String, String>();
        data.put("merchant_id", merchantId);
        data.put("partner_id", partnerId);
        data.put("timestamp", timestamp);
        data.put("sign_type", signType);
        data.put("certificate_type", "ID");
        data.put("certificate_no", bizMerchantReceiver.getMerchIdcard());
        data.put("name", bizMicroInfoByMerchId.getMerchIdcardName());
        data.put("mobile_no", bizMerchantReceiver.getMerchBankMobile());
        String retSign = generateSign(data, signGenerationKey);
        System.out.println("生成的签名为:" + retSign);
        //放入签名后 进行接口请求即可
        data.put("sign", retSign);
        System.out.println("data" + data);
        //   String result = HttpClientHandler.noPictureRequest(url, new Gson().toJson(data));
        String result = doPost(url, new Gson().toJson(data));
        //  String str = HttpUtils.httpPostJson(url, data);
        System.out.println("返回:" + result);
        JSONObject jsonObject = JSONObject.parseObject(result);
        String retCode = jsonObject.getString("ret_code");
        String ret_data = jsonObject.getString("ret_data");
        String ret_msg = jsonObject.getString("ret_msg");
        if ("0000".equals(retCode)) { //成功   //收款者表新增
            JSONObject object = JSONObject.parseObject(ret_data); //要获取那个添加时间
            String add_time = object.getString("add_time");
            //查询出该商户
            BizMerchantReceiver receiver = new BizMerchantReceiver();
            receiver.setMerchId(Long.parseLong(merchId));
            receiver.setUserId(bizMerchantReceiver.getUserId());
            receiver.setMerchName(bizMicroInfoByMerchId.getMerchIdcardName());
            receiver.setMerchIdcard(bizMerchantReceiver.getMerchIdcard());
            receiver.setMerchBankMobile(bizMerchantReceiver.getMerchBankMobile());
            receiver.setMerchBankCardno(bizMerchantReceiver.getMerchBankCardno());
            receiver.setMerchIdcardPositive(bizMerchantReceiver.getMerchIdcardPositive());
            receiver.setContractStatus("0");
            receiver.setMerchIdcardBack(bizMerchantReceiver.getMerchIdcardBack());
            receiver.setCreateTime(add_time);
            //先新增一条商户下发收款者
            iBizMerchantReceiverService.save(receiver);
            ajaxResult.put("ret_msg", ret_msg);
            System.out.println("-----------------" + ret_msg);
            //调取签约
            String signed = Signed(Long.parseLong(merchId));
            return AjaxResult.success(signed);
        }else{
            return AjaxResult.error("ret_msg");
        }
         /*else { //已有收款者 直接去签约
            if ("3".equals(bizMerchantReceiver1.getContractStatus())) {
                return AjaxResult.error("您已签约");
            }
            String signed = Signed(Long.parseLong(merchId));
            return AjaxResult.success(signed);
        }*/
    }




    public final String Signed(Long merchId) throws IOException {
        System.out.println("-----------------------------");
        System.out.println("-----------------------------");
        System.out.println("-----------------------------");
        System.out.println("-----------签约------------------");
        System.out.println("-----------------------------");
        System.out.println("-----------------------------");
        System.out.println("-----------------------------");
        BizMerchantReceiver bizMerchantReceiver = new BizMerchantReceiver();
        bizMerchantReceiver.setMerchId(merchId);
        BizMerchantReceiver bizMerchantReceiver1 = iBizMerchantReceiverService.selectBizMerchantReceiverByMerchId(bizMerchantReceiver);
        String url = "https://b.hndbdj.com/api/contract/signagreement.do";
        SimpleDateFormat df = new SimpleDateFormat("yyyyMMddHHmmss");
        String longTome = df.format(System.currentTimeMillis());
        String createCode = createCode(6);
        String serial_no = longTome + createCode;
        Map<String, String> data = new HashMap<String, String>();
        String s = HexUtils.bytes2Hex(HexUtils.getFileStream(bizMerchantReceiver1.getMerchIdcardPositive()));
        String s1 = HexUtils.bytes2Hex(HexUtils.getFileStream(bizMerchantReceiver1.getMerchIdcardBack()));
        data.put("name", bizMerchantReceiver1.getMerchName()); // 持卡人姓名
        data.put("certificate_image", s); // 证件照正面图像数据
        data.put("certificate_image_background", s1); // 证件照背面图像数据
        data.put("certificate_no", bizMerchantReceiver1.getMerchIdcard()); // 证件号
        data.put("certificate_type", "1"); //证件类型
        data.put("mobile_no", bizMerchantReceiver1.getMerchBankMobile()); // 手机号
        data.put("sign_agreement_type", "ALL"); //签约选择
        data.put("notify_url", "http://www.poshb.cn:8083/pos/receiver/receiver/callBack"); //回调地址 http://www.poshb.cn:8084/pos/receiver/receiver/callBack
        data.put("serial_no", serial_no);//流水号
        data.put("partner_id", partnerId);
        data.put("merchant_id", merchantId);
        String retSign = generateSign(data, signGenerationKey);
        System.out.println("生成的签名为:" + retSign);
        //放入签名后 进行接口请求即可
        data.put("sign", retSign);
        String result = doPost(url, new Gson().toJson(data));
        System.out.println("返回:" + result);
        JSONObject jsonObject = JSONObject.parseObject(result);
        String retCode = jsonObject.getString("ret_code");
        String ret_data = jsonObject.getString("ret_data");
        String ret_msg = jsonObject.getString("ret_msg");
        JSONObject object = JSONObject.parseObject(ret_data);
        if (retCode.equals("0000")) { //代表签约成功
            String serialNo = object.getString("serial_no");
            String deal_no = object.getString("deal_no");
            bizMerchantReceiver1.setSerialNo(serialNo);
            bizMerchantReceiver1.setDealNo(deal_no);
            bizMerchantReceiver1.setContractStatus("2");
            iBizMerchantReceiverService.saveOrUpdate(bizMerchantReceiver1);
            return "正在审核";
        } else { // 签约失败
            bizMerchantReceiver1.setContractStatus("1");
            bizMerchantReceiver1.setErroMessage(ret_msg);
            iBizMerchantReceiverService.saveOrUpdate(bizMerchantReceiver1);
            return "签约失败";
        }
    }

    @ApiOperation("签约回调")
    @PostMapping("/receiver/callBack")
    @Transactional
    public String success(HttpServletRequest request, @RequestBody ReceiverParam param) throws Exception {
        System.out.println("---------回调时间：" + new Date() + "-------------------------------------");
        System.out.println("--------------------------------------------------------------------");
        System.out.println("---------签约回调结果" + param + "----------------------------------------");
        System.out.println("--------------------------------------------------------------------");
        System.out.println("--------------------------------------------------------------------");
        System.out.println("--------------------------------------------------------------------");
        BizMerchantReceiver bizMerchantReceiver = new BizMerchantReceiver();
        if ("S".equals(param.getRet_code())) { //签约成功
            bizMerchantReceiver.setErroMessage(param.getRet_msg());
            bizMerchantReceiver.setContractStatus("3");
            bizMerchantReceiver.setDealNo(param.getDeal_no());
            iBizMerchantReceiverService.updateBizMerchantReceiver(bizMerchantReceiver);
            //        推送消息
            Long userId = iBizMerchantReceiverService.selectUserId(param.getDeal_no());
            BizMessageRecords bizMessageRecords = new BizMessageRecords();
            bizMessageRecords.setMsgUserId(userId);
            bizMessageRecords.setMsgContent("您已签约成功");
            bizMessageRecords.setMsgStatus(0);
            bizMessageRecords.setMsgType(2);
            bizMessageRecords.setReadStatus(0);
            bizMessageRecords.setAdviceType(1);
            bizMessageRecordsService.save(bizMessageRecords);
            return "SUCCESS";
        } else { // 签约失败
            bizMerchantReceiver.setErroMessage(param.getRet_msg());
            bizMerchantReceiver.setContractStatus("1");
            bizMerchantReceiver.setDealNo(param.getDeal_no());
            iBizMerchantReceiverService.updateBizMerchantReceiver(bizMerchantReceiver);
            //        推送消息
            Long userId = iBizMerchantReceiverService.selectUserId(param.getDeal_no());
            BizMessageRecords bizMessageRecords = new BizMessageRecords();
            bizMessageRecords.setMsgUserId(userId);
            bizMessageRecords.setMsgContent("您签约失败");
            bizMessageRecords.setMsgStatus(0);
            bizMessageRecords.setMsgType(2);
            bizMessageRecords.setReadStatus(0);
            bizMessageRecords.setAdviceType(1);
            bizMessageRecordsService.save(bizMessageRecords);
            return "SUCCESS";
        }

    }


    // 点灵工支付接口实现
    @ApiOperation(value = "点灵工接口预支付提现")
    @PostMapping("/pay")
    public AjaxResult pay(@RequestBody CashOutDTO cashOutDTO)
            throws Exception {
        // 获取用户信息
        Long userId = LoginUserUtils.getLoginUserId();
        BizMerchantReceiver bizMerchantReceiver1 = iBizMerchantReceiverService.selectBizMerchantReceiverByUserId(userId);
        if (bizMerchantReceiver1 == null || !bizMerchantReceiver1.getContractStatus().equals("3")) {
            return AjaxResult.error("没有签约");
        }
        // 获取用户信息
        cashOutDTO.setUserId(userId);
        // 提现预支付
        AjaxResult ajaxResult = walletService.payDLG(cashOutDTO);
        return ajaxResult;
    }
    @ApiOperation(value = "点灵工支付接口回调")
    @RequestMapping("/payment/callBack")
    public String paymentCallBack(HttpServletRequest request, @RequestBody ReceiverParam param) {
        DateFormat df = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        String strDate = df.format(new Date());
        System.out.println("-------------------------------" + strDate + "---------------------------------------");
        System.out.println("------------------------------***点灵工支付接口回调支付接口回调***----------------------------");
        System.out.println("-------------------------------------------------------------------------------------");
        System.out.println("进入回调服务.");
        //ReceiverParam apiBaseResult = walletService.deliverapiCallback(param);
        String apiBaseResult = walletService.deliverapiCallbackDLG(param);
        return apiBaseResult;
    }

    //发送json请求
    public String doPost(String url, String data) {
        //创建httpClient对象
        CloseableHttpClient httpClient = HttpClients.createDefault();
        CloseableHttpResponse response = null;
        String result = "";
        try {
            //创建http请求
            HttpPost httpPost = new HttpPost(url);
            httpPost.addHeader("Content-Type", "application/json;charset=utf-8");
            //创建请求内容
            String jsonStr = data;
            StringEntity entity = new StringEntity(jsonStr, "utf-8");
            httpPost.setEntity(entity);
            response = httpClient.execute(httpPost);
            result = EntityUtils.toString(response.getEntity(), "utf-8");
            System.out.println(result);
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            //关闭资源
            if (response != null) {
                try {
                    response.close();
                } catch (IOException ioe) {
                    ioe.printStackTrace();
                }
            }
            if (httpClient != null) {
                try {
                    httpClient.close();
                } catch (IOException ioe) {
                    ioe.printStackTrace();
                }
            }
        }
        return result;
    }



    public static String generateSign(Map<String, String> mapData,
                                      String signGenerationKey) {
        try {
            return generateSign(getSortKVStr(mapData), signGenerationKey);
        } catch (Exception e) {
            System.out.println(e);
            return null;
        }
    }


    public static String generateSign(String sortKVStr, String signGenerationKey) throws Exception {
        StringBuilder sb = new StringBuilder(sortKVStr);
        sb.append("&key=").append(signGenerationKey);
        MessageDigest digest = MessageDigest.getInstance("SHA-256");
        byte[] signBytes = digest.digest(sb.toString().getBytes(Charset.forName("utf-8")));
        return Base64.getEncoder().encodeToString(signBytes);
    }

    private static String getSortKVStr(Map<String, String> values) {

        List<String> keys = new ArrayList<String>();
        keys.addAll(values.keySet());

        Collections.sort(keys);

        StringBuffer sb = new StringBuffer();
        int size = keys.size();
        for (int i = 0; i < size; i++) {
            String key = keys.get(i);
            Object value = values.get(key);

            if (value == null) {
                continue;
            }

            if (value instanceof String && "".equals(value)) {
                continue;
            }

            if (sb.length() > 0) {
                sb.append('&');
            }
            sb.append(key).append("=").append(value);
        }

        String sortKVStr = sb.toString();
        System.out.println("参数排序结果为:" + sortKVStr);
        return sortKVStr;
    }

    /**
     * 随机字符串
     *
     * @param codeLength
     * @return
     */
    public static String createCode(int codeLength) {
        String code = "";
        for (int i = 0; i < codeLength; i++) {
            code += (int) (Math.random() * 9);
        }
        return code;
    }

    @GetMapping("/test")
    public AjaxResult test(@PathVariable String aaa) {
        return AjaxResult.success();
    }
}
